package NIOCommunication;

import java.io.IOException;
import java.nio.channels.ClosedChannelException;
import java.nio.channels.SelectableChannel;
import java.nio.channels.SelectionKey;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;

public class NIOServerSocketContext extends NIOContext
{
	private ServerSocketChannel mServerSocketChannel;
	
	public NIOServerSocketContext(NIOProcessor processor, ServerSocketChannel serverSocketChannel)
	{
		super(processor);
		
		mServerSocketChannel = serverSocketChannel;
		try
		{
			mServerSocketChannel.configureBlocking(false);
			Register();
		}
		catch (IOException e)
		{
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	public NIOServerSocketContext(NIOProcessor processor, int port)
	{
		super(processor);
		
		try
		{
			mServerSocketChannel = ServerSocketChannel.open();
			mServerSocketChannel.configureBlocking(false);
			mServerSocketChannel.socket().bind(new java.net.InetSocketAddress(java.net.InetAddress.getLocalHost(), port));
			System.out.println("ServerSocketChannel address: " + mServerSocketChannel.socket().getInetAddress());
			Register();
		}
		catch (IOException e)
		{
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	public NIOServerSocketContext(NIOProcessor processor)
	{
		this(processor, 9876);
	}
	
	private void Register()
	{
    	try
    	{
			mNIOProcessor.RegisterContextOps(this, SelectionKey.OP_ACCEPT);
		}
    	catch (ClosedChannelException e)
    	{
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	@Override
	public void OnAcceptable(SelectionKey key)
	{
		try
		{
			SocketChannel client = mServerSocketChannel.accept();
			System.out.println("Incoming connection from " + client.socket().getInetAddress());
			OnNewConnection(client);
			NIOSocketContext clientContext = new NIOSocketContext(mNIOProcessor, client);
			
			// register the client with the selector or create a context
		}
		catch (IOException e)
		{
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	public void OnNewConnection(SocketChannel client)
	{
		NIOSocketContext clientContext = new NIOSocketContext(mNIOProcessor, client);
	}

	@Override
	public SelectableChannel GetChannel()
	{
		return mServerSocketChannel;
	}
}
